home *** CD-ROM | disk | FTP | other *** search
- unit Array4U2;
-
- interface
-
- uses
- SysUtils;
-
- const
- {$ifdef Win32}
- MaxSize = 2147483647 div SizeOf(Integer);
- {$else}
- MaxSize = 65535 div SizeOf(Integer);
- {$endif}
-
- type
- PIntArray = ^TIntArray;
- TIntArray = array[0..Pred(MaxSize)] of Integer;
-
- EArrayError = class(Exception);
-
- TIntegerArray = class
- private
- FElements: PIntArray;
- FSize: Integer;
- function GetElement(Index: Integer): Integer;
- procedure SetElement(Index: Integer; const Value: Integer);
- procedure SetSize(const Value: Integer);
- public
- constructor Create(ArraySize: Integer);
- destructor Destroy; override;
- property Element[Index: Integer]: Integer
- read GetElement write SetElement; default;
- property Size: Integer read FSize write SetSize;
- end; { TIntegerArray }
-
- implementation
-
- const
- SOutOfBounds = 'Array index out of bounds';
- STooBig = 'Array size too big';
-
- { TIntegerArray }
-
- constructor TIntegerArray.Create(ArraySize: Integer);
- begin
- inherited Create;
- if ArraySize > MaxSize then
- raise Exception.Create('Array too big');
- { Implicitly call SetSize by writing to the Size property }
- { This means we re-use the ReallocMem and can get rid of the AllocMem }
- Size := ArraySize;
- end;
-
- destructor TIntegerArray.Destroy;
- begin
- if Assigned(FElements) then
- begin
- FreeMem(FElements, FSize * SizeOf(Integer));
- FElements := nil
- end;
- inherited Destroy
- end;
-
- function TIntegerArray.GetElement(Index: Integer): Integer;
- begin
- if (Index < 0) or (Index >= FSize) then
- raise EArrayError.Create(SOutOfBounds);
- Result := FElements^[Index]
- end;
-
- procedure TIntegerArray.SetElement(Index: Integer; const Value: Integer);
- begin
- if (Index < 0) or (Index >= FSize) then
- raise EArrayError.Create(SOutOfBounds);
- FElements^[Index] := Value
- end;
-
- procedure TIntegerArray.SetSize(const Value: Integer);
- begin
- if Value > MaxSize then
- raise Exception.Create(STooBig);
- {$ifdef Win32}
- ReallocMem(FElements, Value * SizeOf(Integer));
- if Value > FSize then
- FillChar(FElements^[FSize], (Value - FSize) * SizeOf(Integer), 0);
- {$else}
- FElements := ReallocMem(FElements, FSize * SizeOf(Integer), Value * SizeOf(Integer));
- {$endif}
- FSize := Value
- end;
-
- end.
-